Road safety is an increasing concern in Metro Manila, aggravated by our averse traffic conditions and increasing use of motorcycles. Fortunately, there's an online platform called DRIVER which contains publicly-available road accident data from 2012 to present. (See below for a screenshot of the website.)
In this notebook, we'll be using the folium
library to generate interactive maps of pedestrian accidents in Metro Manila using the DRIVER dataset.
In [1]:
import pandas as pd
import numpy as np
import folium
pd.set_option("display.max_columns",200)
pd.set_option("display.max_rows",200)
Now let's load the DRIVER dataset.
In [6]:
drivers = pd.read_csv('20170317drivers.csv')
For this map, we only keep the accident records which are related to pedestrians.
In [ ]:
drivers = drivers[drivers['pedestrian']]
For the interactive map, we want to delineate between fatal and non-fatal accidents. Let's make a column which we can use to identify if the record is fatal or non-fatal. Then let's do a quick check of the number of fatal and non-fatal accidents in the dataset.
In [7]:
drivers['fatal_or_not'] = drivers['fatal'].apply(lambda x: 'Fatal' if x == True else 'Non-Fatal')
drivers['fatal_or_not'].value_counts()
Out[7]:
Lastly, let's prepare the pop-up text for each point plotted on the map. We combine the most important features related to each accident, namely:
In [ ]:
drivers['pop_up'] = drivers.apply(lambda x: "Occurred on %s at %s (%s weather) with collision type %s due to factor: %s (Source: %s)" %
(x['occurred_to'], x['location_text'], x['weather'], x['collision type'], x['main cause'], x['reporting agency']), axis=1)
Now let's drop all the other columns we don't need, and only keep the columns we need for generating the interactive map. We also look at the first 5 records of the truncated dataset to check if the contents are correct.
In [10]:
df_dr = drivers[['fatal_or_not', 'lat', 'lon', 'pop_up']].reset_index(drop=True)
df_dr.head()
Out[10]:
We start by generating the DRIVER feature group, which essentially puts all data points plotted in that feature group in the same layer. This will come in handy when we add the layer control toggle for the interactive map, especially if we add more layers on top of this.
In [ ]:
driver = folium.FeatureGroup(name='DRIVER 2011-2017')
Next, we initialize the map using a preset central location, zoom start, and tile set. We use the cartodbdark_matter
tile set for good contrast against our color choice.
In [ ]:
sample_map = folium.Map(location=[14.555555, 121.0027], tiles='cartodbdark_matter', zoom_start=11)
Next, we plot each record in the DRIVERS dataset, and distinguish between fatal and non-fatal points using color. Fatal points have the color Terracotta Red, whereas non-fatal points are in yellow.
In [ ]:
for fatality, group in df_dr.groupby('fatal_or_not'):
if fatality == 'Fatal':
for row in group.index:
folium.CircleMarker(location=[group.ix[row, 'lat'], group.ix[row,'lng']], popup="(Source: DRIVER)"+group.ix[row,'pop_up'], radius=50, color=None, fill_color='#ef4631').add_to(driver)
else:
for row in group.index:
folium.CircleMarker(location=[group.ix[row, 'lat'], group.ix[row,'lng']], popup="(Source: DRIVER)"+group.ix[row,'pop_up'], radius=50, color=None, fill_color='#f9cf55').add_to(driver)
driver.add_to(sample_map)
Lastly, we then add the layer control button in the interactive map to be able to toggle the layer on/off, then save the map as an HTML file which can be opened in any browser.
In [20]:
# Add layer control button to upper right to be able to toggle the layer on/off.
folium.map.LayerControl().add_to(sample_map)
# save map
sample_map.save('Pedestrian Casualties (DRIVER).html')
We can also quickly view the map within the jupyter notebook environment. And voila! We have an interactive map of pedestrian casualties in the DRIVERS dataset.
In [21]:
sample_map
Out[21]: